<?php

namespace app\model\system;

use app\model\BaseModel;
use think\model\concern\SoftDelete;

/**
 * 系统消息模型
 * 
 * @property int $id 主键ID
 * @property int $sender_id 发送人ID
 * @property int $receiver_id 接收人ID
 * @property string $title 消息标题
 * @property string $content 消息内容
 * @property string $type 消息类型：system系统 notice通知 task任务 remind提醒
 * @property int $is_read 是否已读：0未读 1已读
 * @property string $link_url 跳转链接
 * @property string $extra_data 额外数据(JSON)
 * @property int $send_time 发送时间
 * @property int $read_time 阅读时间
 * @property int $create_time 创建时间
 * @property int $update_time 更新时间
 * @property int $delete_time 删除时间
 */
class Message extends BaseModel
{
    use SoftDelete;

    protected $name = 'oa_message';
    protected $pk = 'id';

    // 消息类型常量
    const TYPE_SYSTEM = 'system';   // 系统消息
    const TYPE_NOTICE = 'notice';   // 通知公告
    const TYPE_TASK = 'task';       // 任务消息
    const TYPE_REMIND = 'remind';   // 提醒消息
    const TYPE_APPROVAL = 'approval'; // 审批消息
    const TYPE_WORKFLOW = 'workflow'; // 工作流消息

    // 字段类型转换
    protected $type = [
        'id' => 'integer',
        'sender_id' => 'integer',
        'receiver_id' => 'integer',
        'is_read' => 'integer',
        'send_time' => 'timestamp',
        'read_time' => 'timestamp',
        'create_time' => 'timestamp',
        'update_time' => 'timestamp',
        'delete_time' => 'timestamp',
    ];

    /**
     * 关联发送人
     */
    public function sender()
    {
        return $this->belongsTo('app\model\admin\User', 'sender_id', 'id');
    }

    /**
     * 关联接收人
     */
    public function receiver()
    {
        return $this->belongsTo('app\model\admin\User', 'receiver_id', 'id');
    }

    /**
     * 获取消息列表
     */
    public static function getList($params = [])
    {
        $query = self::with(['sender', 'receiver']);

        // 按接收人筛选
        if (!empty($params['receiver_id'])) {
            $query->where('receiver_id', $params['receiver_id']);
        }

        // 按发送人筛选
        if (!empty($params['sender_id'])) {
            $query->where('sender_id', $params['sender_id']);
        }

        // 按类型筛选
        if (!empty($params['type'])) {
            $query->where('type', $params['type']);
        }

        // 按阅读状态筛选
        if (isset($params['is_read'])) {
            $query->where('is_read', $params['is_read']);
        }

        // 按关键词搜索
        if (!empty($params['keyword'])) {
            $query->where(function($q) use ($params) {
                $q->where('title', 'like', '%' . $params['keyword'] . '%')
                  ->whereOr('content', 'like', '%' . $params['keyword'] . '%');
            });
        }

        return $query->order('id desc')->paginate($params['limit'] ?? 15);
    }

    /**
     * 获取未读消息数量
     */
    public static function getUnreadCount($receiver_id)
    {
        return self::where('receiver_id', $receiver_id)
            ->where('is_read', 0)
            ->count();
    }

    /**
     * 获取未读消息列表
     */
    public static function getUnreadList($receiver_id, $limit = 10)
    {
        return self::with(['sender'])
            ->where('receiver_id', $receiver_id)
            ->where('is_read', 0)
            ->order('id desc')
            ->limit($limit)
            ->select();
    }

    /**
     * 发送消息
     */
    public static function send($data = [])
    {
        $message = new self();
        $message->sender_id = $data['sender_id'] ?? 0; // 0表示系统消息
        $message->receiver_id = $data['receiver_id'];
        $message->title = $data['title'];
        $message->content = $data['content'];
        $message->type = $data['type'] ?? self::TYPE_SYSTEM;
        $message->link_url = $data['link_url'] ?? '';
        $message->extra_data = !empty($data['extra_data']) ? json_encode($data['extra_data']) : '';
        $message->send_time = time();
        $message->is_read = 0;

        return $message->save();
    }

    /**
     * 批量发送消息
     */
    public static function sendBatch($receiver_ids, $data = [])
    {
        $messages = [];
        foreach ($receiver_ids as $receiver_id) {
            $messages[] = [
                'sender_id' => $data['sender_id'] ?? 0,
                'receiver_id' => $receiver_id,
                'title' => $data['title'],
                'content' => $data['content'],
                'type' => $data['type'] ?? self::TYPE_SYSTEM,
                'link_url' => $data['link_url'] ?? '',
                'extra_data' => !empty($data['extra_data']) ? json_encode($data['extra_data']) : '',
                'send_time' => time(),
                'is_read' => 0,
                'create_time' => time(),
                'update_time' => time(),
            ];
        }

        return self::insertAll($messages);
    }

    /**
     * 标记为已读
     */
    public static function markAsRead($message_ids, $receiver_id)
    {
        if (is_numeric($message_ids)) {
            $message_ids = [$message_ids];
        }

        return self::where('receiver_id', $receiver_id)
            ->where('id', 'in', $message_ids)
            ->where('is_read', 0)
            ->update([
                'is_read' => 1,
                'read_time' => time()
            ]);
    }

    /**
     * 标记全部已读
     */
    public static function markAllAsRead($receiver_id)
    {
        return self::where('receiver_id', $receiver_id)
            ->where('is_read', 0)
            ->update([
                'is_read' => 1,
                'read_time' => time()
            ]);
    }

    /**
     * 获取消息统计
     */
    public static function getStats($receiver_id)
    {
        $stats = self::where('receiver_id', $receiver_id)
            ->field([
                'COUNT(*) as total',
                'SUM(CASE WHEN is_read = 0 THEN 1 ELSE 0 END) as unread',
                'SUM(CASE WHEN type = "system" THEN 1 ELSE 0 END) as system_count',
                'SUM(CASE WHEN type = "notice" THEN 1 ELSE 0 END) as notice_count',
                'SUM(CASE WHEN type = "task" THEN 1 ELSE 0 END) as task_count',
                'SUM(CASE WHEN type = "remind" THEN 1 ELSE 0 END) as remind_count',
                'SUM(CASE WHEN type = "approval" THEN 1 ELSE 0 END) as approval_count',
                'SUM(CASE WHEN type = "workflow" THEN 1 ELSE 0 END) as workflow_count',
            ])
            ->find();

        return $stats;
    }

    /**
     * 获取类型文本
     */
    public function getTypeTextAttr($value, $data)
    {
        $typeMap = [
            self::TYPE_SYSTEM => '系统消息',
            self::TYPE_NOTICE => '通知公告',
            self::TYPE_TASK => '任务消息',
            self::TYPE_REMIND => '提醒消息',
            self::TYPE_APPROVAL => '审批消息',
            self::TYPE_WORKFLOW => '工作流消息',
        ];
        return $typeMap[$data['type']] ?? '未知';
    }

    /**
     * 获取额外数据
     */
    public function getExtraDataAttr($value)
    {
        return $value ? json_decode($value, true) : [];
    }

    /**
     * 搜索器：按接收人ID
     */
    public function searchReceiverIdAttr($query, $value)
    {
        $query->where('receiver_id', $value);
    }

    /**
     * 搜索器：按类型
     */
    public function searchTypeAttr($query, $value)
    {
        $query->where('type', $value);
    }

    /**
     * 搜索器：按阅读状态
     */
    public function searchIsReadAttr($query, $value)
    {
        $query->where('is_read', $value);
    }

    /**
     * 搜索器：按关键词
     */
    public function searchKeywordAttr($query, $value)
    {
        $query->where(function($q) use ($value) {
            $q->where('title', 'like', '%' . $value . '%')
              ->whereOr('content', 'like', '%' . $value . '%');
        });
    }
}